/******************************************************
 * @file encoding_manager.c
 * @author Destiny 
 * @brief 解码模块管理程序
 * 
 * @version 0.1
 * @date 2024-07-18
 *****************************************************/
#include <config.h>
#include <encoding_manager.h>
#include <string.h>
#include <stdlib.h>

static PT_EncodingOpr g_ptEncodingOprHead;   /*解码模块链表头*/
/*
 * @description		    	: 向框架注册一个解码模块
 * @param - ptEncodingOpr 	: 需要注册的调试模块结构体指针
 * @return 			    	: 0 成功;其他 失败
 */
int RegisterEncodingOpr(PT_EncodingOpr ptEncodingOpr)
{
	PT_EncodingOpr ptTmp;

	if (!g_ptEncodingOprHead)
	{
		g_ptEncodingOprHead   = ptEncodingOpr;
		ptEncodingOpr->ptNext = NULL;
	}
	else
	{
		ptTmp = g_ptEncodingOprHead;
		while (ptTmp->ptNext)
		{
			ptTmp = ptTmp->ptNext;
		}
		ptTmp->ptNext	      = ptEncodingOpr;
		ptEncodingOpr->ptNext = NULL;
	}

	return 0;
}
/*
 * @description		    : 依据名称得到对应解码模块结构体指针
 * @param - pcName   	: 解码模块名称
 * @return 			    : 成功 解码模块结构体指针;失败 NULL
 */
PT_EncodingOpr Encode(char *pcName)
{
	PT_EncodingOpr ptTmp = g_ptEncodingOprHead;
	
	while (ptTmp)
	{
		if (strcmp(ptTmp->name, pcName) == 0)
		{
			return ptTmp;
		}
		ptTmp = ptTmp->ptNext;
	}
	return NULL;
}
/*
 * @description		    : 打印所有解码模块名称
 * @param - ptDebugOpr 	: 无
 * @return 			    : 无
 */
void ShowEncodingOpr(void)
{
	int i = 0;
	PT_EncodingOpr ptTmp = g_ptEncodingOprHead;

	while (ptTmp)
	{
		printf("%02d %s\n", i++, ptTmp->name);
		ptTmp = ptTmp->ptNext;
	}
}
/*
 * @description		    	: 根据文件头选择一种解码方式
 * @param - pucFileBufHead 	: 文件头
 * @return 			    	: 成功 解码模块结构体指针;失败 NULL
 */
PT_EncodingOpr SelectEncodingOprForFile(uint8_t *pucFileBufHead)
{
	PT_EncodingOpr ptTmp = g_ptEncodingOprHead;

	while (ptTmp)
	{	
		if (ptTmp->isSupport(pucFileBufHead))
			return ptTmp;
		else
			ptTmp = ptTmp->ptNext;
	}
	return NULL;
}
/*
 * @description		    	: 解码得到对应unicode编码，默认为UTF-8方式
 * @param - pucBufStart 	: 文件当前读取起始地址
 * @param - pucBufEnd 		: 文件尾部地址
 * @param - pdwCode 		: unicode编码
 * @return 			    	: 编码字节数 成功;其他 失败
 */
int GetCodeFrmBuf(uint8_t *pucBufStart, uint8_t *pucBufEnd, uint32_t *pdwCode)
{
    return Encode("utf-8")->GetCodeFrmBuf(pucBufStart, pucBufEnd, pdwCode);
}
/*
 * @description		    	: 向解码模块添加指定字体库
 * @param - ptEncodingOpr 	: 目标解码模块
 * @param - ptFontOpr 		: 字体库对象
 * @return 			    	: 0 成功;其他 失败
 */
int AddFontOprForEncoding(PT_EncodingOpr ptEncodingOpr, PT_FontOpr ptFontOpr)
{
	PT_FontOpr ptFontOprCpy;
	
	if (!ptEncodingOpr || !ptFontOpr)  //非空
	{
		return -1;
	}
	else
	{ 
		ptFontOprCpy = malloc(sizeof(T_FontOpr));
		if (!ptFontOprCpy)
		{
			return -1;
		}
		else
		{
            
			memcpy(ptFontOprCpy, ptFontOpr, sizeof(T_FontOpr));   //拷贝一个字库对象副本
			ptFontOprCpy->ptNext = ptEncodingOpr->ptFontOprSupportedHead;   //插入链表中
			ptEncodingOpr->ptFontOprSupportedHead = ptFontOprCpy;
			return 0;
		}		
	}
}
/*
 * @description		    	: 从解码模块中删除指定字体库
 * @param - ptEncodingOpr 	: 目标解码模块
 * @param - ptFontOpr 		: 字体库对象
 * @return 			    	: 0 成功;其他 失败
 */
int DelFontOprFrmEncoding(PT_EncodingOpr ptEncodingOpr, PT_FontOpr ptFontOpr)
{
	PT_FontOpr ptTmp;
	PT_FontOpr ptPre;
		
	if (!ptEncodingOpr || !ptFontOpr)  //非空
	{
		return -1;
	}
	else
	{
		/*找到对应字体库对象，并移除*/
		ptTmp = ptEncodingOpr->ptFontOprSupportedHead;
		if (strcmp(ptTmp->name, ptFontOpr->name) == 0)
		{
			
			ptEncodingOpr->ptFontOprSupportedHead = ptTmp->ptNext;
			free(ptTmp);
			return 0;
		}

		ptPre = ptEncodingOpr->ptFontOprSupportedHead;
		ptTmp = ptPre->ptNext;
		while (ptTmp)
		{
			if (strcmp(ptTmp->name, ptFontOpr->name) == 0)
			{
				
				ptPre->ptNext = ptTmp->ptNext;
				free(ptTmp);
				return 0;
			}
			else
			{
				ptPre = ptTmp;
				ptTmp = ptTmp->ptNext;
			}
		}
		return -1;
	}
}
/*
 * @description		    	: 解码模块初始化
 * @param - 			 	: 无
 * @return 			    	: 0 成功;其他 失败
 */
int EncodingInit(void)
{
	int iError;

	iError = AsciiEncodingInit();
	if (iError)
	{
		DBG_PRINTF(DLOG_LVL_ERROR,DLOG_TAG,"AsciiEncodingInit error!\n");
		return -1;
	}

	iError = Utf16leEncodingInit();
	if (iError)
	{
		DBG_PRINTF(DLOG_LVL_ERROR,DLOG_TAG,"Utf16leEncodingInit error!\n");
		return -1;
	}
	
	iError = Utf16beEncodingInit();
	if (iError)
	{
		DBG_PRINTF(DLOG_LVL_ERROR,DLOG_TAG,"Utf16beEncodingInit error!\n");
		return -1;
	}
	
	iError = Utf8EncodingInit();
	if (iError)
	{
		DBG_PRINTF(DLOG_LVL_ERROR,DLOG_TAG,"Utf8EncodingInit error!\n");
		return -1;
	}
	return 0;
}